<template>
  <!-- 右侧消息内容  -->
  <div class="message">
    <!-- 头部 -->
    <div class="header">
      <span class="name-span">
        {{ friend?.name }}
      </span>
      <el-tag class="ml-2" type="warning" v-if="friend?.role === 0">管理员</el-tag>
      <el-tag class="ml-2" v-if="friend?.role === 1">教师</el-tag>
      <el-tag class="ml-2" type="success" v-if="friend?.role === 2">学生</el-tag>
    </div>
    <!-- 消息 -->
    <div class="content" ref="contentRef">
      <el-scrollbar class="content-scroll" ref="scrollbarRef" @scroll="scroll">
        <template v-for="msg in msgList" :key="msg.id">
          <!--左边的聊天样式 -->
          <div class="left msg" v-if="msg.uid !== userInfo.id">
            <div class="msg-item">
              <div class="avatar">
                <el-avatar
                  class="img"
                  :icon="UserFilled"
                  :src="friend?.avatar"
                  shape="square"
                  alt=""
                />
              </div>
              <span class="span">{{ msg.content }}</span>
            </div>
            <span class="time">{{ formatMsgTime(msg.time) }}</span>
          </div>
          <!--右边的聊天 -->
          <div class="right msg" v-if="msg.uid === userInfo.id">
            <div class="msg-item">
              <span class="span">{{ msg.content }}</span>
              <div class="avatar">
                <el-avatar
                  class="img"
                  :icon="UserFilled"
                  :src="userInfo.avatar"
                  shape="square"
                  @click="handleToInfo"
                />
              </div>
            </div>
            <span class="time">{{ formatMsgTime(msg.time) }}</span>
          </div>
        </template>
      </el-scrollbar>
    </div>

    <!-- 输入框 -->
    <div class="text">
      <div class="input">
        <textarea
          placeholder="请输入内容"
          v-model="sendMsg"
          ref="input"
          v-focus
          @keydown.enter.prevent="send"
        ></textarea>
      </div>
      <button class="btn" type="success" @click="send">发送(Enter)</button>
    </div>
  </div>
</template>

<script setup>
import {
  ref,
  onMounted,
  nextTick,
  computed,
  onBeforeMount,
  watch,
  onUnmounted,
  onUpdated,
  inject
} from 'vue'
import { UserFilled } from '@element-plus/icons-vue'
import { useStore } from 'vuex'
import { useRoute, useRouter } from 'vue-router'
import { binMsg } from '@/global/api.js'
import { formatMsgTime } from '@/utils/formatDate.js'
import { getUserById } from '@/services/roleCommon.js'

// --- 变量 ---
const store = useStore()
const route = useRoute()
const router = useRouter()
const userInfo = computed(() => store.state.userModule.userInfo)
const friendList = computed(() => store.state.friendModule.friendList)
const scrollbarRef = ref(null)
const contentRef = ref(null)
const friend = ref(null)
const sendMsg = ref('') // 发送的消息
// 消息列表
const msgList = computed(() => store.state.messageModule.msgList)
// 获取仓库中已经连接好的 socket实例
const socket = store.state.userModule.socket

// 监听返回给自己私聊消息，
socket.on('back', (e) => {
  // 更新自己好友列表中的最新消息和最新时间
  store.commit('friendModule/updateFriendList', {
    id: e.fid,
    time: e.time,
    content: e.content
  })
  // 添加消息到聊天列表，并发起请求将消息保存到数据库
  store.dispatch('messageModule/insertMsg', e)
  goButtom()
})

// 监听私聊信息
socket.on('receive', (e) => {
  // 收到消息，就更新好友列表中对应的好友的最新消息和最新时间
  store.commit('friendModule/updateFriendList', {
    id: e.uid,
    time: e.time,
    content: e.content
  })
  // 如果当前的会话窗口，不是发消息过来的好友，让未读消息数+1
  if (route.params.id !== e.uid) {
    store.commit('friendModule/updateUnreadCount', { id: e.uid })
  } else {
    // 如果窗口是发信息过来的好友，将消息添加到聊天列表中，并且将消息状态更新为已读
    const promise = new Promise((resolve, reject) => {
      store.commit('messageModule/addMsg', e)
      setTimeout(() => {
        resolve()
      }, 200)
    })
    promise.then(() => {
      // 等消息添加到列表，100毫秒后再去后端更新消息状态
      store.dispatch('messageModule/updateMsgState', {
        uid: e.fid,
        fid: e.uid,
        test: 1
      })
      goButtom()
    })
  }
})

// --- 方法 ---
// 发送消息
const send = () => {
  binMsg().closeAll()
  // console.log(userInfo.value);
  if (sendMsg.value.trim() === '') return binMsg('warning', '不能发送空白信息')
  const msg = {
    uid: userInfo.value.id,
    fid: friend.value.id,
    urole: userInfo.value.role,
    content: sendMsg.value,
    state: false,
    time: Date.now()
  }
  // 发送消息到服务端
  socket.emit('send', msg)
  sendMsg.value = ''
  goButtom()
}

// 获取好友信息
const getFriend = async () => {
  if (route.query.role) {
    const { data: res } = await getUserById(parseInt(route.query.role), route.params.id)
    friend.value = res.data.data
  }
}

// 获取聊天消息
const getMessage = () => {
  store.dispatch('messageModule/getMessage', {
    uid: userInfo.value.id,
    fid: route.params.id,
    page_num: 1
  })
  // 先判断好友是否存在未读消息
  friendList.value.forEach((item) => {
    if (item.id === route.params.id) {
      if (item.unReadCount > 0) {
        // 前端更改好友未读消息数量
        store.commit('friendModule/updateMsgStateInFront', route.params.id)
        // 后端更改好友未读消息数量
        store.dispatch('messageModule/updateMsgState', {
          uid: userInfo.value.id,
          fid: route.params.id
        })
      }
    }
  })
}

// 滚动到底部
const goButtom = (id) => {
  // console.log(id);
  nextTick(() => {
    // 问题：聊天列表没有加载出来，滚动的高度还是最初的高度
    // * 暂时用定时器这么处理
    setTimeout(() => {
      scrollbarRef.value.setScrollTop(scrollbarRef.value.wrap$.scrollHeight)
      // console.log(scrollbarRef.value.wrap$.scrollHeight)
    }, 500)
  })
}

// 滚动条的滚动事件
const scroll = ({ scrollTop }) => {
  // binMsg().closeAll()
  // if (scrollTop === 0) {
  //   binMsg('warning', '没有更多数据了')
  // }
}

const handleToInfo = () => {
  router.push('/home/personal/info')
}

// --- 监听器，生命周期 ---
// 传入的friend信息变化，就滚动到底部
watch(
  () => route.params.id,
  (val) => {
    if (val) {
      getFriend()
      getMessage()
      goButtom()
    }
    // 清空输入框
    sendMsg.value = ''
  }
)

onMounted(() => {
  getFriend()
  getMessage()
  goButtom()
})

onUnmounted(() => {
  console.log('销毁了')
})
</script>

<style lang="less" scoped>
.message {
  position: relative;
  flex: 1;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  background-color: #f5f5f5;

  .header {
    position: relative;
    width: 100%;
    height: 48px;
    line-height: 48px;
    border-bottom: 1px solid #e7e7e7;
    .name-span {
      padding-left: 28px;
      font-size: 18px;
      color: black;
      padding-right: 10px;
    }
  }

  .content {
    // flex: 1;
    width: 100%;
    // height: calc(600px - 48px - 130px);
    height: calc(600px - 48px - 150px);
    overflow: auto;

    // 聊天信息的公共样式
    .msg {
      padding: 0 22px;
      position: relative;
      .msg-item {
        display: flex;
        padding: 10px;
        .avatar {
          width: 38px;
          height: 38px;
          user-select: none;
          .img {
            width: 100%;
            height: 100%;
            cursor: pointer;
          }
        }
        .span {
          // max-width: 440px;
          max-width: 300px;
          display: block;
          color: #232323;
          margin-left: 10px;
          border-radius: 5px;
          padding: 10px 10px 10px 10px;
          font-family: PingFangSC-Regular;
          word-break: break-all; // 字母强制换行
        }
      }
      .time {
        position: relative;
        top: -10px;
        font-size: 8px;
        color: rgba(51, 51, 51, 0.399);
        user-select: none;
      }
    }

    // 左边的聊天样式
    .left {
      .msg-item {
        margin-bottom: 14px;
        .span {
          background-color: #fdfdfd;
          margin-left: 12px;
          position: relative;
        }
        .span:before {
          content: '';
          position: absolute;
          top: 10px;
          left: -16px;
          width: 0;
          height: 0;
          border-style: solid;
          border-width: 10px 10px;
          border-color: transparent #fff transparent transparent;
        }
      }
      .time {
        position: absolute;
        left: 89px;
        top: -10px;
      }
    }

    // 右边的聊天样式
    .right {
      .msg-item {
        justify-content: right;
        margin-bottom: 14px;
        .span {
          background-color: #cad9ff;
          margin-right: 12px;
          position: relative;
        }
        .span:after {
          content: '';
          position: absolute;
          top: 11px;
          right: -16px;
          width: 0;
          height: 0;
          border-style: solid;
          border-width: 9px 10px;
          border-color: transparent transparent transparent #cad9ff;
        }
      }
      .time {
        position: absolute;
        right: 86px;
      }
    }
  }

  .text {
    position: relative;
    width: 100%;
    height: 130px;
    border-top: 1px solid #e7e7e7;
    // overflow: scroll;

    .input {
      width: 100%;

      textarea {
        padding: 15px 28px 0 28px;
        width: calc(100% - 56px);
        height: 75px;
        background-color: #f5f5f5;
        // 去除默认样式
        outline: none;
        border: none;
        resize: none;
      }
    }
    .btn {
      position: absolute;
      bottom: 10px;
      right: 28px;
      // background-color: #e9e9e9;
      // color: #409eff;
      background-color: #409eff;
      color: #fff;
      border: none;
      padding: 9px 15px;
      font-size: 14px;
      border-radius: 7px;
    }
    .btn:hover {
      background-color: #56a9fb;
      cursor: pointer;
    }
  }
}

/deep/ .el-scrollbar__wrap {
  padding-top: 20px !important;
}

// 滚动条
.input textarea::-webkit-scrollbar {
  /*滚动条整体样式*/
  width: 6px; /*高宽分别对应横竖滚动条的尺寸*/
  // height: 5px;
}
.input textarea::-webkit-scrollbar-thumb {
  /*滚动条里面小方块*/
  border-radius: 3px;
  // box-shadow: inset 0 0 5px rgba(255, 255, 255, 0.774);
  background: #d2d2d2;
}
</style>
